home *** CD-ROM | disk | FTP | other *** search
/ Windows News 2010 Summer - Disc 1 / WN_Ete2010_CD1.iso / Onglet5 / Weezo / Weezo setup.exe / {code_appDir} / www / ext / image.php < prev    next >
PHP Script  |  2010-05-19  |  18KB  |  464 lines

  1. <?php
  2. /**
  3.  * Display (and if requested resample) an image located out of document root
  4.  *
  5.  * parameters are passed with GET method :
  6.  * file : file name (including full path), url encoded
  7.  * (optional) w, h : width and height of image
  8.  *
  9.  * script should be called like : <img src="/ext/image.php?file=c%3foo.jpg&w=32&h=32"> or through cfExtImage function
  10.  *
  11.  * PHP version 5
  12.  *
  13.  * LICENSE: This source file is subject to version 3.0 of the PHP license
  14.  * that is available through the world-wide-web at the following URI:
  15.  * http://www.php.net/license/3_0.txt.  If you did not receive a copy of
  16.  * the PHP License and are unable to obtain it through the web, please
  17.  * send a note to license@php.net so we can mail you a copy immediately.
  18.  *
  19.  * @category   NA
  20.  * @package    NA
  21.  * @author     Nicolas Bruley / Peer 2 World <contact@weezo.net>
  22.  * @copyright  2005-2009 Nicolas Bruley / Peer 2 World
  23.  * @license    http://www.php.net/license/3_0.txt  PHP License 3.0
  24.  * @version    CVS: $Id:$
  25.  * @link       http://www.weezo.net
  26.  * @since      File available since Release 1.1.0
  27.  */
  28.  
  29.  
  30. /**
  31.  * @desc Generate and sent image and headers to ouptut
  32.  *
  33.  * @param string $completeFilename
  34.  * @param array $uri: parsed URI
  35.  */
  36. function imageGenerate($completeFilename,$uri){
  37.     // Image rotation
  38.     if(isset($uri['rot']) && is_numeric($uri['rot'])) $rotation=$uri['rot']; else $rotation=0;
  39.  
  40.     // Resample quality (get resource-level values before closing session)
  41.     $resampleQuality=cfHGetVar('imageResampleQuality',DEFAULT_RESIZE_METHOD);
  42.  
  43.     // JPG quality (get resource-level values before closing session)
  44.     $JPGQuality=cfHGetVar('thumbnailJPGQuality',DEFAULT_JPG_QUALITY);
  45.  
  46.  
  47.     // Stretch small images (get resource-level values before closing session)
  48.     $stretchSmallImages=cfRGetVar('stretchSmallImages');
  49.  
  50.     //close session
  51.     $speedLimit=cfUGetVar('downloadSpeedLimit');
  52.     wSession_write_close(); unset($_SESSION);
  53.     set_time_limit(0);
  54.  
  55.     // Headers
  56.     header('Keep-Alive: timeout=15, max=2000');
  57.     header('Proxy-Connection: Keep-Alive');
  58.  
  59.     // No cache
  60.     if(isset($uri['cache']) && $uri['cache']=='0') WHeaders::noCache();
  61.  
  62.     // Cache
  63.     else WHeaders::cache($completeFilename);
  64.  
  65.     if(!isset($uri['w'])) $uri['w']=0; if(!isset($uri['h'])) $uri['h']=0;
  66.  
  67.     require(INCLUDE_DIR.'mime_type.php');
  68.  
  69.     /**
  70.      * File's icon
  71.      */
  72.     if(isset($uri['icon'])){
  73.         header('Content-Type: image/png');
  74.         require_once(INCLUDE_DIR.'explorerFunctions.php');
  75.         // Extract icon from file
  76.         if(!($ico=efExtractIcon($completeFilename,false,((isset($uri['w']))?$uri['w']:16),array('icoPngCheck'=>1)))) {
  77.             require_once(INCLUDE_DIR.'outputFunctions.php');
  78.             $ico=file_get_contents(cfAppDocRoot().efIcon($completeFilename,false));
  79.         }
  80.         die($ico);
  81.     }
  82.  
  83.     /**
  84.      * Audio files: extract cover
  85.      */
  86.     if(substr(mimeType($completeFilename),0,5)=='audio')
  87.         imageExtractAudioCover($completeFilename,((isset($uri['w']))?$uri['w']:0),((isset($uri['h']))?$uri['h']:0),!isset($uri['noDC']));
  88.  
  89.     /**
  90.      * Images
  91.      */
  92.     if(substr(mimeType($completeFilename),0,5)=='image'){
  93.         // if resize requested, generate resized image and send it to output
  94.         if($rotation || $uri['w'] || $uri['h'] || (isset($uri['sq']) && $uri['sq'])){
  95.             header('Content-Type: image/jpeg');
  96.             if($uri['w'] || $uri['h'])
  97.                 $res=cfCreateResizedJPG($completeFilename, 0, 0, 'return', $uri['w'], $uri['h'], $resampleQuality, $JPGQuality, $rotation, (isset($uri['sq']) && $uri['sq']), $stretchSmallImages);
  98.             else
  99.                 $res=cfCreateResizedJPG($completeFilename, 0, 0, 'return', 0, 0, $resampleQuality, $JPGQuality, $rotation, (isset($uri['sq']) && $uri['sq']), $stretchSmallImages);
  100.             // Stream result to output
  101.             if($res) cfStreamString($res, $speedLimit);
  102.         }
  103.         //If no resize and no rotation requested, directly send image to output
  104.         else{
  105.             $ext=strtolower(substr($completeFilename,strrpos($completeFilename,'.')+1));
  106.             // browser supported extension : stream
  107.             if($ext=='jpg' || $ext=='gif' || $ext=='jpeg' || $ext=='png' || $ext=='itc' || $ext=='itc2') {
  108.                 if($ext=='jpg' || $ext=='jpeg') header('Content-Type: image/jpeg');
  109.                 if($ext=='png' || $ext=='itc' || $ext=='itc2') header('Content-Type: image/png');
  110.                 if($ext=='gif') header('Content-Type: image/gif');
  111.                 if($ext=='ico') header('Content-Type: image/x-icon');
  112.  
  113.                 // Stream file to output
  114.                 if($ext=='itc')
  115.                     cfStreamString(substr(file_get_contents($completeFilename),500),$speedLimit);
  116.                 elseif($ext=='itc2')
  117.                     cfStreamString(substr(file_get_contents($completeFilename),492),$speedLimit);
  118.                 else
  119.                     cfStreamFile($completeFilename,false,$speedLimit);
  120.                 $res=true;
  121.             }
  122.             // unsupported: (try to) convert to jpg
  123.             else {
  124.                 header('Content-Type:image/jpeg');
  125.                 $res=cfCreateResizedJPG($completeFilename,0,0,"",0,0,$resampleQuality, $JPGQuality, 0,false, $stretchSmallImages);
  126.                 // Stream result to output
  127.                 if($res) cfStreamString($res,$speedLimit);
  128.             }
  129.         }
  130.         // If image couldn't  be generated, return empty image
  131.         if(!$res) echo file_get_contents(cfAppDocRoot().'/gfx/dot.jpg');
  132.  
  133.         // Update debug buffer
  134.         if(cfMGetVar('debugAsync'))    cfDebugUpdateBuffer('DONE '.basename($completeFilename).' '.(($uri['w'] || $uri['h'])?' resampled:'.$uri['w'].'x'.$uri['h']:''));
  135.         exit;
  136.     }
  137.  
  138.     /**
  139.      * Other files
  140.      */
  141.     @unlink(cfAppDataDir().'/thumbnail.tmp.jpg');
  142.     // Generate resized image with createJPG
  143.     if(!cfGGetVar('disableCreateJPG') && cfStreamProc('"'.cfAppBinDir().'/createJPG.exe" "'.$completeFilename.'" "'.cfAppDataDir().'/thumbnail.tmp.jpg" '.(($uri['w'])?$uri['w']:'160').' '.(($uri['h'])?$uri['h']:'120').' all no 100 '.$JPGQuality,array('stdout'=>'return'))!='NOK'
  144.         && file_exists(cfAppDataDir().'/thumbnail.tmp.jpg')){
  145.         header('Content-Type: image/jpeg');
  146.         echo file_get_contents(cfAppDataDir().'/thumbnail.tmp.jpg');
  147.         @unlink(cfAppDataDir().'/thumbnail.tmp.jpg');
  148.     }
  149.     else{
  150.  
  151.         header('Content-Type: image/jpeg');
  152.         imagejpeg(imagecreatetruecolor((($uri['w'])?$uri['w']:'160'),(($uri['h'])?$uri['h']:'120')));
  153.     }
  154. }
  155.  
  156. /**
  157.  * @desc Check published image access rights and send to output
  158.  *
  159.  * @param array $uri: parsed URI
  160.  */
  161. function imagePublished($uri){
  162.     $id=$uri['dlToken'];
  163.  
  164.     require_once(INCLUDE_DIR.'explorerFunctions.php');
  165.     $tokenList=efTokensRead();
  166.     if(!isset($tokenList[$id]) || $tokenList[$id]['type']!=='publishImage') logError('invalid published video id ('.$id.')');
  167.     $token=$tokenList[$id];
  168.  
  169.     // Check file's existence
  170.     if(!is_file($token['filename'])) logError('perempted published image ('.$token['filename'].')');
  171.  
  172.     // Increase number of downloads and save
  173.     $tokenList[$id]['limitNb']--;
  174.     efTokensWrite($tokenList);
  175.  
  176.     // Full-size image
  177.     if(isset($uri['w']) && isset($uri['h']) && $uri['w']==0 && $uri['h']==0 && @$token['fullsizeAllowed']) imageGenerate($token['filename'],array('w'=>0,'h'=>0));
  178.  
  179.     // Resized image
  180.     imageGenerate($token['filename'],array('w'=>$token['w'],'h'=>$token['h']));
  181. }
  182.  
  183. /**
  184.  * @desc Send a resized version of an image located into /gfx dir or subdir
  185.  *
  186.  * @param array $uri: parsed URI
  187.  */
  188. function imageResizedGFX($uri){
  189.     // Check if browser is requesting a cached image, and if so, just return not-modified-file header
  190.     checkCache();
  191.  
  192.     $completeFilename=$uri['file'];
  193.     $completeFilename=cfAppDocRoot().str_replace('..','',$completeFilename);
  194.     if(!is_file($completeFilename)) logError('extImage: NX '.$completeFilename.' doesnt exist');
  195.  
  196.     header('Last-Modified: '.gmdate("D, d M Y H:i:s",@filemtime($completeFilename)).' GMT');
  197.     header('Etag: "'.md5($_SERVER['REQUEST_URI']).'"');
  198.     header('Content-Type:image/jpeg');
  199.  
  200.     cfCreateResizedJPG($completeFilename, 0, 0, '', $uri['w'], $uri['h'], 2, 75, 0, false, true);
  201.     exit;
  202. }
  203.  
  204. /**
  205.  * @desc Generate an image with error message, and log error
  206.  *
  207.  * @param string $logCaption : error message
  208.  */
  209. function logError($logCaption){
  210.     global $uri;
  211.  
  212.     cfLog($logCaption, LOG_ER);
  213.     cfDebugUpdateBuffer('ERROR: '.$logCaption);
  214.  
  215.     $winDir=isset($_SERVER['SystemRoot'])?str_replace('\\','/',$_SERVER['SystemRoot']):'c:/windows';
  216.  
  217.     // Send headers with no-cache
  218.     WHeaders::noCache();
  219.     WHeaders::contentType("Content-type: image/png");
  220.     $capt=str_replace('extImage: ','',$logCaption);
  221.     $capt=substr($capt,0,floor(strlen($capt)/3))."\n".substr($capt,floor(strlen($capt)/3),floor(strlen($capt)/3))."\n".substr($capt,-floor(strlen($capt)/3));
  222.  
  223.     // Generate black image with a ? watermark
  224.     $w=(isset($uri['w']) && $uri['w'])?$uri['w']:(int)(5*strlen($capt)/3);
  225.     $h=(isset($uri['h']) && $uri['h'])?$uri['h']:(int)(5*strlen($capt)/3);
  226.     $im = imagecreatetruecolor($w, $h);
  227.     imagefilledrectangle($im, 0, 0, $w, $h, imagecolorallocate($im, 0, 0, 0));
  228.     $tw=floor(3*min($w,$h)/4);
  229.     $th=$tw; $tw*=0.75;
  230.     $se = imagecreatetruecolor($tw,$th);
  231.     imagettftext($se, $th, 0, $tw*0/16, $th, imagecolorallocate($im, 45, 45, 45), $winDir.'/fonts/arial.ttf', '?');
  232.     imagecopy($im,$se,floor(($w-$tw)/2),floor(($h-$th)/2),0,0,$tw,$th);
  233.  
  234.     imagepng($im);
  235.     imagedestroy($im);
  236.  
  237.     exit;
  238. }
  239.  
  240. /**
  241.  * @desc return not-modified-file header
  242.  *
  243.  */
  244. function return304(){
  245.     header('HTTP/1.x 304 Not Modified');
  246.     header('X-Powered-By:');
  247.     header("Date: " . gmdate("D, d M Y H:i:s") . " GMT");
  248.     header('Etag: "'.md5($_SERVER['REQUEST_URI']).'"');
  249.     header('Content-Length');
  250.     header('Content-Type');
  251.     exit;
  252. }
  253.  
  254. /**
  255.  * @desc Check if browser is requesting a cached image, and if so, just return not-modified-file header
  256.  *
  257.  * @param string $completeFilename: filename including path
  258.  */
  259. function checkCache($completeFilename=false){
  260.     global $uri;
  261.     if(isset($uri['cache']) && $uri['cache']=='0') return false;
  262.  
  263.     $headers=getallheaders();
  264.     if(!isset($headers['If-Modified-Since']) && !isset($headers['If-None-Match'])) return false;
  265.     if(isset($headers['If-None-Match']) && $headers['If-None-Match']!='"'.md5($_SERVER['REQUEST_URI']).'"') return false;
  266.     if(isset($headers['If-Modified-Since']) && $completeFilename){
  267.         if(!($date=strtotime($headers['If-Modified-Since']))) return304();
  268.         if($date<@filemtime($completeFilename)) return false;
  269.     }
  270.     return304();
  271. }
  272.  
  273. /**
  274.  * @desc Extract and send audio file's cover to output
  275.  *
  276.  * @param string $completeFilename
  277.  * @param integer $width: ouput width
  278.  * @param integer $height: ouput height
  279.  * @param bool $directoryCover: false not to use directory cover if no embeded cover found
  280.  */
  281. function imageExtractAudioCover(&$completeFilename,$width=0,$height=0,$directoryCover=true){
  282.     $ext=cfFileExtension($completeFilename);
  283.  
  284.     /**
  285.      * MP3 ID3 image
  286.      */
  287.     if($ext=='mp3'){
  288.         require(INCLUDE_DIR.'miscFunctions.php');
  289.         $cover=new id3V2Ext($completeFilename);
  290.         // ID3 embeded image: generate and send to output
  291.         if($cover->hasImage()) $cover->generate($width,$height);
  292.     }
  293.  
  294.     /**
  295.      * WMA embedded image
  296.      */
  297.     elseif($ext=='wma' || $ext=='wmv' || $ext=='asf'){
  298.         // Get embedded image
  299.         require(INCLUDE_DIR.'php-reader/ASF.php');
  300.         $asf=@new ASF($completeFilename);
  301.         if(isset($asf->header->extendedContentDescription->descriptors['WM/Picture'])){
  302.             $v=$asf->header->extendedContentDescription->descriptors['WM/Picture'];
  303.  
  304.             // Dirty parsing of WM/Picture data
  305.             $pos=0;
  306.             while($v[$pos]!='i' && $pos<50 && $pos<strlen($v))    $pos++;
  307.             if($v[$pos]=='i'){
  308.                 $epos=$pos;
  309.                 while(substr($v,$pos,2)!="\0\0" && $pos<50)    $pos++;
  310.                 $mimeType=str_replace("\0",'',substr($v,$epos,$pos-$epos));
  311.                 while($v[$pos]=="\0" && $pos<strlen($v)) $pos++;
  312.                 // Resized image
  313.                 if($width && $height){
  314.                     if($in=@imagecreatefromstring(substr($v,$pos))){
  315.                         header('Content-Type: image/jpeg');
  316.                         $out=imagecreatetruecolor($width,$height);
  317.                         fastimagecopyresampled($out,$in,0,0,0,0,$width,$height,imagesx($in),imagesy($in),3);
  318.                         imagejpeg($out,null,70);
  319.                         imagedestroy($in);
  320.                         imagedestroy($out);
  321.                         exit;
  322.                     }
  323.                 }
  324.                 // Original image
  325.                 else{
  326.                     header('Content-Type: '.$mimeType);
  327.                     echo substr($v,$pos);
  328.                     exit;
  329.                 }
  330.             }
  331.         }
  332.     }
  333.  
  334.     // ISO14496 format
  335.     elseif($ext=='3gp'||$ext=='3gpp'||$ext=='avc'||$ext=='dcf'||$ext=='m21'||$ext=='m4a'||$ext=='m4b'||$ext=='m4p'||$ext=='m4v'||$ext=='maf'||$ext=='mj2'||$ext=='mjp'||$ext=='mov'||$ext=='mp4'||$ext=='odf'||$ext=='sdv'||$ext=='qt'||$ext=='aac'){
  336.         require_once('ISO14496.php');
  337.         $isom=new ISO14496($completeFilename,array("base" => "moov.udta.meta.ilst"));
  338.  
  339.         if (isset($isom->moov->udta->meta->ilst)) {
  340.             $ilst = $isom->moov->udta->meta->ilst;
  341.             if (isset($ilst->covr)) {
  342.                 if($width && $height){
  343.                     header('Content-type: image/jpeg');
  344.                     if(($pos=strpos($ilst->covr,' ╪'))===false) // JPEG
  345.                         $pos=strpos($ilst->covr,'ëPNG'); // PNG
  346.                     if($pos!==false && ($in=imagecreatefromstring(substr($ilst->covr,$pos)))){
  347.                         header('Content-Type: image/jpeg');
  348.                         $out=imagecreatetruecolor($width,$height);
  349.                         fastimagecopyresampled($out,$in,0,0,0,0,$width,$height,imagesx($in),imagesy($in),3);
  350.                         imagejpeg($out,null,70);
  351.                         imagedestroy($in);
  352.                         imagedestroy($out);
  353.                         exit;
  354.                     }
  355.                 }
  356.                 else{
  357.                     if ($ilst->covr->data->hasFlag(ISO14496_Box_DATA::JPEG))
  358.                         header("Content-Type: image/jpeg");
  359.                     elseif ($ilst->covr->data->hasFlag(ISO14496_Box_DATA::PNG))
  360.                         header("Content-Type: image/png");
  361.                     echo $ilst->covr->data->value;
  362.                 }
  363.             }
  364.         }
  365.     }
  366.     // Else, look for best image in folder
  367.     if ($directoryCover){
  368.         require_once(INCLUDE_DIR.'explorerFunctions.php');
  369.         $completeFilename=efGetCoverFromFolder($completeFilename, $score);
  370.     }
  371.     else {
  372.         header('Content-type: image/jpeg');
  373.         cfCreateResizedJPG(cfAppDocRoot().'/gfx/cd.png',80,80,'',$width,$height);
  374.         exit;
  375.     }
  376. }
  377.  
  378.  
  379. // Decode and parse URI
  380. $uri=cfParseExtURI();
  381.  
  382. // DEBUG
  383. if(cfMGetVar('debugAsync'))    cfDebugSetBuffer('image',$uri,'...');
  384.  
  385. // Published image
  386. if(isset($uri['dlToken'])) imagePublished($uri);
  387.  
  388. // Simple resized gfx
  389. if(isset($uri['file']) && substr($uri['file'],0,5)=='/gfx/') imageResizedGFX($uri);
  390.  
  391.  
  392. /**
  393.  * Regular redirected images below this point
  394.  */
  395.  
  396. wSession_start_nowrite();
  397. header('P3P: policyref="/w3c/p3p.xml",CP="NON COR CURa OUR NOR NAV"');
  398.  
  399. // Verify that user logged in
  400. if (!isset($_SESSION['userLogged'])) logError('extImage: UL '.$_SERVER['REQUEST_URI'].' unlogged access attempt');
  401.  
  402. // Set active resource
  403. if(isset($uri['resId'])&& is_numeric($uri['resId']) && isset($_SESSION['res'][$uri['resId']]) && is_array($_SESSION['res'][$uri['resId']])) $_SESSION['activeResourceId']=$uri['resId'];
  404.  
  405. // Check that a file is passed
  406. if(!isset($uri['file'])) logError('extImage: NI No passed image');
  407. $completeFilename=$uri['file'];
  408.  
  409.  
  410. // Shared list
  411. if(cfSharedMode('list') && strpos($completeFilename,'*resourceDataDirBasePath*')===false) $completeFilename=cfSharedCompleteFilename($completeFilename);
  412.  
  413. // Shared folder
  414. else{
  415.     // Don't debug-log images from resource data dir
  416.     if(strpos($completeFilename,'*resourceDataDirBasePath*')!==false) {
  417.         $_ENV['cfStreamFileNoLog']=1;
  418.         $completeFilename=str_replace('*resourceDataDirBasePath*',cfAppResourceDir(),$completeFilename);
  419.     }
  420.     else $completeFilename=str_replace('*resourceBasePath*',cfRGetVar('path'),$completeFilename);
  421. }
  422.  
  423. // Check if browser is requesting a cached image, and if so, just return not-modified-file header
  424. checkCache($completeFilename);
  425.  
  426. /**
  427.  * Check access rights
  428.  */
  429.  
  430. // Resource specific file source and rights function : bypass common file's existence and access rights
  431. // and (may) replace given file name by real file name
  432. if(cfRGetVar('extAccessFunction')) {
  433.     $extAccessFunction = create_function('$completeFilename', cfRGetVar('extAccessFunction'));
  434.     if(!($completeFilename=$extAccessFunction($completeFilename))) logError('extImage: DA '.$_SERVER['REQUEST_URI'].' denied access');
  435. }
  436. // Administration, allow exe viewing
  437. elseif (isset($uri['icon']) && cfUGetVar('administrator') && cfRGetVar('type')=='administration'){}
  438. else{
  439.     // If file doesn't exist but is located into resource data directory and is an image and thumbnails allowed for this resource, generate
  440.     // (might happend if a problem occurs with createJPG)
  441.     if(!file_exists($completeFilename) && cfFileExtension($completeFilename)=='jpg' &&
  442.         cfIsSubDir(cfRGetVar('resourceDataDir'),$completeFilename) && cfRGetVar('resourceDataDirAccessAllowed') && cfRGetVar('path') &&
  443.         cfRGetVar('photoThumbnailsNeeded') && ($tmw=cfRGetVar('thumbnailMaxWidth')) &&
  444.         substr(basename($completeFilename),0,strlen($tmw))==$tmw){
  445.             $sourceCompleteFilename=cfJoinPathFile(cfRGetVar('path'),substr(dirname($completeFilename),strlen(cfRGetVar('resourceDataDir'))));
  446.             $sourceCompleteFilename.='/'.substr(cfFileWithoutExtension(basename($completeFilename)),strlen(cfRGetVar('thumbnailMaxWidth')));
  447.             // Verify that source file access is allowed
  448.             if(cfFileRights($sourceCompleteFilename,'download')){
  449.                 // Everything is OK, thumbnail can be generated
  450.                 cfCreateResizedJPG($sourceCompleteFilename,0,0,$completeFilename,cfRGetVar('thumbnailMaxWidth'),cfRGetVar('thumbnailMaxHeight'),false,false,0,cfRGetVar('cropThumbnails'));
  451.             }
  452.     }
  453.     if(!cfFileRights($completeFilename,'download')) logError('extImage: DA '.$completeFilename.' denied access');
  454.  
  455.     //Verifies file's existence
  456.     if(!is_file($completeFilename)) logError('extImage: NX '.$completeFilename.' doesnt exist');
  457. }
  458.  
  459.  
  460.  
  461.  
  462. // Generate and sent image and headers to ouptut
  463. imageGenerate($completeFilename,$uri)
  464. ?>